package 图书管理项目.Dao;

import 图书管理项目.Book;
import 图书管理项目.DBUtil;

import javax.xml.transform.Result;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

//用来访问 Book数据的对象
public class BookDao {
    //1.新增书籍  （插入）
    public boolean add(Book book) {
        //把 book 对象插入到数据库的book表中

        Connection connection=null;//创建Connection引用
        PreparedStatement statement=null;//创建PreparedStatement引用

        try {
            //1.和数据库建立连接
            connection = DBUtil.getConnection();
            //2.拼装SQL语句
            String sql="insert into book values(null,?,?,?,?,?)";
            statement=connection.prepareStatement(sql);
            statement.setString(1,book.getName());
            statement.setString(2,book.getAuthor());
            statement.setInt(3,book.getPrice());
            statement.setString(4,book.getType());
            statement.setInt(5,book.isBorrowed()?1:0);

            //3.执行SQL语句
            int ret=statement.executeUpdate();
            if (ret!=1) {
                //ret不等于1，则插入失败，返回false
                return false;
            }
            //插入成功
            return true;

        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            //4.释放资源
            DBUtil.close(connection,statement,null);
        }
        return false;  //出现异常时最终返回false
    }
    //2.查看所有书籍 （查找）
    //  获取数据库表中的所有书籍记录
    public List<Book> selectAll() {
        List<Book> books=new ArrayList<>();

        Connection connection=null;
        PreparedStatement statement =null;
        ResultSet resultSet=null;

        try{
            //1.和数据库建立连接
            connection=DBUtil.getConnection();

            //2.拼装SQL语句
            String sql="select * from book ";
            statement=connection.prepareStatement(sql);

            //3.执行SQL语句
            resultSet=statement.executeQuery();

            //4.遍历结果集  -->类似Iterator迭代器的遍历
            while (resultSet.next()) {
                //取出表的每一行，即每条记录，构造一个Book对象
                //根据每一条记录，按照每一列要求的内容逐一设置book信息
                Book book=new Book();
                book.setBookId(resultSet.getInt("bookId"));
                book.setName(resultSet.getString("name"));
                book.setAuthor(resultSet.getString("author"));
                book.setPrice(resultSet.getInt("price"));
                book.setType(resultSet.getString("type"));
                //book.setBorrowed(resultSet.getInt("isBorrowed")==1?true:false);
                book.setBorrowed(resultSet.getInt("isBorrowed")==1);

                //将当前的book对象添加到最终的 ArrayList
                books.add(book);
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            //5.释放资源
            DBUtil.close(connection,statement,resultSet);
        }
        return books;

    }
    //3.根据名字找书籍 （查找）
    public List<Book> selectByName(String name) {
        List<Book> books=new ArrayList<>();


        Connection connection=null;
        PreparedStatement statement=null;
        ResultSet resultSet=null;

        try {
            //1.和数据库建立连接
            connection=DBUtil.getConnection();

            //2.构造SQL语句
            String sql="select * from book where name=?";
            statement=connection.prepareStatement(sql);
            statement.setString(1,name);

            //3.执行SQL语句
            resultSet = statement.executeQuery();

            //4.遍历结果集
            while(resultSet.next()) {
                Book book=new Book();
                book.setBookId(resultSet.getInt("bookId"));
                book.setName(resultSet.getString("name"));
                book.setAuthor(resultSet.getString("author"));
                book.setPrice(resultSet.getInt("price"));
                book.setType(resultSet.getString("type"));
                book.setBorrowed(resultSet.getInt("isBorrowed")==1);

                books.add(book);
            }
        } catch (SQLException e) {
            e.printStackTrace();

        } finally {
            //5.释放资源
            DBUtil.close(connection,statement,resultSet);
        }
        return books;
    }

    //4.删除书籍  （删除）
    public boolean delete(int bookId1) {
        Connection connection=null;
        PreparedStatement statement=null;

        try {
            //1.和数据库建立连接
            connection=DBUtil.getConnection();
            //2.构造SQL语句
            String sql="delete from book where bookId=?";
            statement=connection.prepareStatement(sql);
            statement.setInt(1,bookId1);
            //3.执行SQL语句
            int ret=statement.executeUpdate();
            if (ret!=1) {
                return false;//删除失败
            }
            return true;

        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            //4.释放资源
            DBUtil.close(connection,statement,null);
        }
        return false;//出现异常时最终返回false
    }


    //5.借书      （修改）
    public boolean borrowBook(int bookId1) {
        Connection connection=null;
        PreparedStatement statement1=null;
        PreparedStatement statement2=null;//创建PreparedStatement引用
        ResultSet resultSet=null;

        try {
            //1.和数据库建立连接
            connection=DBUtil.getConnection();//第一次创建 Connection

            //2.构造SQL语句
            // 当前 isBorrowed 已经为1，还能借吗？
            // 如果传入的 bookId1 不存在，即不存在书，还能借吗?
            // 因此，需要先查找，确认书存在 且 未被借出

            //先查找书
            String sql="select  * from book where bookId=?";
            statement1=connection.prepareStatement(sql);//第一次创建 PreparedStatement
            statement1.setInt(1,bookId1);

            //3.执行SQL语句
            resultSet=statement1.executeQuery();//第一次创建 ResultSet
            //注意：resultSet中要么1条结果，要么0条结果
            if (resultSet.next()) {
                //进入条件说明 该书存在,紧接着判断这本书是否借出，等于1则为借出
                boolean isBorrowed=(resultSet.getInt("isBorrowed")==1);
                if (isBorrowed) {
                    System.out.println("bookId="+bookId1+"该书已借出！");
                    return false;
                }
            }else {
                System.out.println("bookId="+bookId1+"书不存在，无法借出！");
                return false;
            }

            //开始借书
            //构造SQL
            sql="update book set isBorrowed=1 where bookId=?";
            statement2=connection.prepareStatement(sql);//第二次创建 PreparedStatement！！！
            statement2.setInt(1,bookId1);
            //执行SQL
            int ret=statement2.executeUpdate();
            if (ret!=1) {
                return false;
            }
            return true;
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            //4.释放资源，注意这里释放的 statement引用指向的 第二次创建的PreparedStatement
            //这就导致 statement引用之前第一次持有PreparedStatement对象 不能 被手动关闭
            //这就需要，垃圾回收机制　GC释放这个对象，但这并不稳妥，还是将　对象分别记录下来，手动分别释放更为稳妥
            //DBUtil.close(connection,statement,resultSet);
            if (resultSet!=null) {
                try {
                    resultSet.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
            if (statement2!=null) {
                try {
                    statement2.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
            if (statement1!=null) {
                try {
                    statement1.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }

            if (connection!=null) {
                try {
                    connection.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
        }
        return false;
    }


    //6.还书      （修改）
    public boolean returnBook(int bookId) {
        Connection connection=null;
        PreparedStatement statement1=null;
        PreparedStatement statement2=null;
        ResultSet resultSet=null;

        try {
            //1.和数据库建立连接
            connection=DBUtil.getConnection();

            //2.构造SQL语句
            //先查找还的书是否存在,并且是否借出
            String sql="select * from book where bookId=?";
            statement1=connection.prepareStatement(sql);
            statement1.setInt(1,bookId);
            //3.执行SQL
            resultSet=statement1.executeQuery();
            if (resultSet.next()) {
                //说明书存在，
                //再判断当前书是否被借出，如果 未借出则不能归还
                boolean isBorrowed=(resultSet.getInt("isBorrowed")==0);
                if (isBorrowed) {
                    System.out.println("bookId="+bookId+"书未被借出，无法归还");
                    return false;
                }
            }else {
                //说明书不存在，无法借出
                System.out.println("bookId="+bookId+"不存在");
                return false;
            }

            //2.构造SQL语句
            //开始归还书
            //书存在 且  已借出
            sql="update book set isBorrowed=0 where bookId=?";
            statement2=connection.prepareStatement(sql);
            statement2.setInt(1,bookId);
            //3.执行SQL
            int ret=statement2.executeUpdate();
            if (ret!=1) {
                return false;
            }
            return true;

        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            //4.释放资源，注意这里释放的 statement引用指向的 第二次创建的PreparedStatement
            //这就导致 statement引用之前第一次持有PreparedStatement对象 不能 被手动关闭
            //这就需要，垃圾回收机制　GC释放这个对象，但这并不稳妥，还是将　对象分别记录下来，手动分别释放更为稳妥
            //DBUtil.close(connection,statement,resultSet);
            if (resultSet!=null) {
                try {
                    resultSet.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
            if (statement2!=null) {
                try {
                    statement2.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
            if (statement1!=null) {
                try {
                    statement1.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }

            if (connection!=null) {
                try {
                    connection.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
        }
        return false;
    }

}
